
#
# Որոշյալ ինտեգրալի հաշվարկը
#
proc integral { rule fun a b {epsilon 0.01} } {
  if { [expr {abs($b - $a)}]< $epsilon } then {
    return [apply $rule $fun $a $b]
  }
  
  set m [expr {($a + $b) / 2.0}]
  set so [integral $rule $fun $a $m]
  set si [integral $rule $fun $m $b]
  return [expr {$so + $si}]
}

proc simpson { f a b } {
  set fa [apply $f $a]
  set fb [apply $f $b]
  set fm [apply $f [expr {($a + $b) / 2.0}]]
  return [expr {(($b - $a) / 6.0) * ($fa + 4.0 * $fm + $fb)}]
}

proc trapezoid { f a b } {
  set fa [apply $f $a]
  set fb [apply $f $b]
  return [expr {($b - $a) * ($fa + $fb) / 2.0}]
}

proc func name {
  return [list [info args $name] [info body $name]]
}

#
# TEST
#
puts [integral [func simpson] {x { return [expr {$x * $x}] }} 1 2]
puts [integral [func simpson] {x { return [expr {$x * $x * $x}] }} 1 2]
puts [integral [func simpson] {x { return [expr {tan($x)}] }} 1 2]


